package com.zhixing.reward.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.zhixing.reward.domain.entity.Reward;
import com.zhixing.reward.domain.enums.RewardStatus;
import com.zhixing.reward.domain.vo.RewardVO;
import com.zhixing.reward.mapper.RewardMapper;
import com.zhixing.reward.service.RewardService;
import lombok.RequiredArgsConstructor;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import java.math.BigDecimal;
import java.time.LocalDate;
import java.time.YearMonth;
import java.util.List;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

import static com.zhixing.common.constant.Constant.*;

@Service
@RequiredArgsConstructor
public class RewardServiceImpl implements RewardService {

    private final RewardMapper rewardMapper;
    private final RedisTemplate<String, Object> redisTemplate;

    public Reward getReward(Integer userId, Boolean isNewcomer) {
        String name = isNewcomer ? NEWCOMER_REWARD : DAILY_REWARD;
        BigDecimal[] amount = isNewcomer ? NEWCOMER_REWARD_AMOUNT : DAILY_REWARD_AMOUNT;
        Integer[] orderNumber = isNewcomer ? NEWCOMER_REWARD_ORDER_NUMBER : DAILY_REWARD_ORDER_NUMBER;
        return new Reward(null, userId, name, amount[0], orderNumber[0], RewardStatus.NOT_RECEIVE, amount[1],
            orderNumber[1], RewardStatus.NOT_RECEIVE, amount[2], orderNumber[2], RewardStatus.NOT_RECEIVE, YearMonth.now().toString());
    }

    @Override
    public void sendNewcomerReward(Integer userId) {
        // 开启新人奖励和日常奖励
        List<Reward> rewards = List.of(getReward(userId, true), getReward(userId, false));
        rewardMapper.insert(rewards);
    }

    @Override
    public List<RewardVO> getRewardInfo(Integer userId) {
        // 查询缓存
        String key = ZHIXING_REWARD_INFO + userId;
        List<RewardVO> rewardVOList = Objects.requireNonNull(redisTemplate.opsForList().range(key, 0, -1))
                .stream().map(o -> (RewardVO) o).toList();
        if (CollUtil.isNotEmpty(rewardVOList)) return rewardVOList;

        // 查询数据库
        LambdaQueryWrapper<Reward> lqw = new LambdaQueryWrapper<Reward>()
                .eq(Reward::getUserId, userId).eq(Reward::getYearMonth, YearMonth.now().toString());
        List<Reward> rewards = rewardMapper.selectList(lqw);
        if (CollUtil.isEmpty(rewards)) {
            // 如果数据库中没有数据，则开启日常任务
            Reward reward = getReward(userId, false);
            rewardMapper.insert(reward);
            rewards.add(reward);
        }
        rewardVOList = BeanUtil.copyToList(rewards, RewardVO.class);

        // 存入缓存，如果是当月的最后一天就不用存入缓存了
        if (LocalDate.now().getDayOfMonth() != LocalDate.now().lengthOfMonth()) {
            redisTemplate.opsForList().rightPushAll(key, rewardVOList.toArray(new RewardVO[0]));
            redisTemplate.expire(key, ONE_DAY_SECOND, TimeUnit.SECONDS);
        }
        return rewardVOList;
    }
}
